// pages/ledger/ledger.js
const FS = wx.getFileSystemManager()
const WXfilePath = wx.env.USER_DATA_PATH
const FILETYPE = ".json"
const isOpenConsole = false // true 开启console  false 关闭

Page({

	/**
	 * 页面的初始数据
	 */
	data: {
		fileList: [], // 根目录
		monthFileList: [], // 本月文件目录
		tableData: [],
		fileName: "hello",

		files: [],
		isScanning: false,
		scannedFolders: 0,
		totalSize: '0 B', // 用户文件大小
	},

	/**
	 * 生命周期函数--监听页面加载
	 */
	onLoad(options) {
		this.getFileData()
	},
	// 删除文件目录
	removeFileDirStorage() {
		let fs_fileList = FS.readdirSync(wx.env.USER_DATA_PATH)
		wx.showActionSheet({
			itemList: fs_fileList,
			success: (res) => {
				this.removeDir(this.getTodayFilePath(fs_fileList[res.tapIndex]).dirName)
			}
		})
	},
	// 页面测试按钮点击事件
	createFileTest() {
		this.createFile(this.getTodayFilePath().filePath)
	},
	insertDataTest() {
		this.insertData("抽烟测试写入", 0, "1", "小李同学")
	},
	removeFileTest() {
		this.removeFile(this.getTodayFilePath().filePath)
	},
	removeDirTest() {
		this.removeDir(this.getTodayFilePath().dirName)
	},
	getFileDataTest() {
		this.getFileData()
	},

	// 文件内数据操作
	// 文件内数据操作
	// 文件内数据操作
	// 文件内数据操作
	// 文件内数据操作
	// 文件内数据操作

	insertData(purpose, money, author, authorLabel) {
		let that = this
		let todayFilePath = this.getTodayFilePath()
		// 本次插入数据
		let writeData = {
			id: todayFilePath.timestamp,
			datetime: todayFilePath.datetime,
			purpose: purpose,
			money: money,
			author: author,
			authorLabel
		}
		if (!purpose) {
			return wx.showToast({
				title: "干啥花的钱写上",
				icon: "none"
			})
		}
		if (money < 0) {
			return wx.showToast({
				title: "元子咋还填负了呢",
				icon: "none"
			})
		}
		if (!author) {
			return wx.showToast({
				title: "支出人选了嘛",
				icon: "none"
			})
		}
		this.data.tableData.push(writeData)
		this.setData({
			tableData: this.data.tableData
		})
		let writeResultData = JSON.stringify(this.data.tableData)
		console.log("正在准备插入数据", writeResultData)
		// 判断文件/目录是否存在
		FS.access({
			path: todayFilePath.filePath,
			success(res) {
				console.log("今日文件已创建", res)
				// 文件数据，先删后插
				that.removeFile(todayFilePath.filePath).then(clearRes => {
					that.createFile(todayFilePath.filePath, writeResultData)
				})
			},
			fail(err) {
				console.log("今日文件未创建", err)
				that.createFile(todayFilePath.filePath, writeResultData)
			}
		})
	},

	// 获取指定文件内数据
	getFileData(filePath) {
		let that = this
		filePath = !filePath ? this.getTodayFilePath().filePath : filePath
		wx.showLoading({
			title: "正在获取今日账单"
		})
		// 判断文件/目录是否存在
		console.log("查看是否存在文件", filePath)
		FS.access({
			path: filePath,
			success(res) {
				console.log("获取指定文件内数据-今日文件已创建", res)
				let fileData = FS.readFileSync(filePath, 'utf8')
				if (!fileData) {
					return wx.showToast({
						title: `文件：${filePath},暂无数据！`,
						icon: "none",
						duration: 5000
					})
				}
				try {
					that.setData({
						tableData: JSON.parse(fileData)
					})
					console.warn(`查看${filePath}文件内信息`, that.data.tableData)
					isOpenConsole ? console.table(that.data.tableData) : ""
				} catch (e) {
					//TODO handle the exception
					console.error(`${filePath}文件JSON串格式解析失败`, fileData ? fileData : "文件内无数据")
				}
			},
			fail(err) {
				if (err && err.errMsg.indexOf("fail no such file or directory")) {
					console.log("获取指定文件内数据-今日文件未创建", err)
					that.insertData("机器操作-零元购", 0, "机器小李")
				} else {
					console.error("获取指定文件内数据-getFileData", err)
				}
			},
			complete(com) {
				wx.hideLoading()
			}
		})
	},








	// 文件操作
	// 文件操作
	// 文件操作
	// 文件操作
	// 文件操作

	// 获取今日文件名称
	getTodayFilePath(fileName) {
		let result = ""
		let now = new Date();
		let year = now.getFullYear(); // 年
		let month = (now.getMonth() + 1).toString().padStart(2, '0'); // 月，注意getMonth()是从0开始的
		let date = now.getDate().toString().padStart(2, '0'); // 日
		let hours = now.getHours().toString().padStart(2, '0'); // 时
		let minutes = now.getMinutes().toString().padStart(2, '0'); // 分
		let seconds = now.getSeconds().toString().padStart(2, '0'); // 秒
		let timestamp = now.getTime();

		result = `${WXfilePath}/${year}-${month}/${year}-${month}-${date}${FILETYPE}`
		return {
			filePath: result, // 文件路径
			dirName: `${WXfilePath}/${fileName?fileName:year+"-"+month}`, // 文件目录
			dateMonth: `${year}-${month}`, // 当前月份
			datetime: `${year}-${month}-${date} ${hours}:${minutes}:${seconds}`, // 操作时间
			timestamp: timestamp, // 操作时间戳
		}
	},
	// 创建文件
	createFile(filePath, jsonData) {
		let that = this
		if (!filePath) {
			return
		}

		FS.access({
			path: filePath,
			success(res) {
				wx.showToast({
					title: "文件已存在，无需重复创建",
					icon: "none"
				})
			},
			fail(err) {
				FS.writeFile({
					filePath: filePath,
					data: jsonData,
					encoding: 'utf8',
					success(res) {
						console.log("文件创建成功", res)
						that.getFileList()
					},
					fail(err) {
						console.error("文件创建失败,准备创建本月目录文件夹", err)
						FS.mkdir({
							dirPath: that.getTodayFilePath().dirName,
							recursive: false,
							success(dirRes) {
								console.log("本月目录创建成功，正在自动重新创建文件", dirRes)
								that.createFile(filePath, jsonData)
							},
							fail(dirErr) {
								console.error("本月目录创建失败，原因如下1", dirErr)
								console.error("本月目录创建失败，原因如下2", filePath, jsonData)

								wx.showToast({
									title: "文件管理服务错误，请联系你老公尽快解决呦",
									icon: "none",
									duration: 5000
								})
							}
						})
					}
				})
			}
		})
	},

	// 删除文件
	removeFile(filePath) {
		let that = this
		return new Promise((resolve, reject) => {
			if (!filePath) {
				reject()
			}

			console.warn("正在准备删除文件", filePath)
			// 判断文件/目录是否存在
			FS.access({
				path: filePath.toString(),
				success(res) {
					// 文件存在
					FS.unlink({
						filePath,
						success: (res) => {
							console.log("文件删除成功", res)
							that.getFileList()
							resolve()
						},
						fail: err => {
							console.error(`文件${filePath}删除失败`, err)
							wx.showToast({
								title: "文件删除失败",
								icon: "none"
							})
							reject()
						}
					})
				},
				fail(err) {
					// 文件不存在或其他错误
					console.error("文件目录还不存在的呦", err)
					wx.showToast({
						title: "文件目录还不存在的呦",
						icon: "none"
					})
					resolve()
				}
			})
		})
	},
	// 删除指定月分数据目录
	removeDir(dirPath) {
		if (!dirPath) {
			return
		}
		if (dirPath.indexOf("miniprogramLog") != -1) {
			wx.showToast({
				title: '系统文件，禁止删除',
				icon: "none"
			})
			return console.error(dirPath, "文件目录不可以删除")
		}
		console.warn("正在准备删除目录", dirPath)
		// 判断文件/目录是否存在
		FS.access({
			path: dirPath.toString(),
			success(res) {
				// 目录存在
				FS.rmdir({
					dirPath: dirPath.toString(),
					recursive: true,
					success: dirRes => {
						console.log(`${dirPath}文件夹删除成功`, dirRes)
						wx.showToast({
							title: `${dirPath}文件夹删除成功`,
							icon: "none"
						})
					},
					fail: err => {
						console.error(`${dirPath}文件夹删除失败`, err)
						wx.showToast({
							title: `${dirPath}文件夹删除失败`,
							icon: "none"
						})
					}
				})
			},
			fail(err) {
				// 文件不存在或其他错误
				console.error("文件目录还不存在的呦", err)
				wx.showToast({
					title: "文件目录还不存在的呦",
					icon: "none"
				})
			}
		})
	},

	// 获取已存在的文件列表
	getFileList() {
		let result = FS.readdirSync(wx.env.USER_DATA_PATH)
		console.warn("查看文件列表", result)
		isOpenConsole ? console.table(result) : ""
		this.setData({
			fileList: result
		})
		return result
	},
	// 获取已存在的文件列表
	getMonthFileList() {
		let that = this
		return new Promise((resolve, reject) => {
			let fileMonth = that.getTodayFilePath().dateMonth
			let dirPath = WXfilePath + "/" + fileMonth
			// let dirPath = WXfilePath + "/2025-10"

			FS.access({
				path: dirPath.toString(),
				success(res) {
					// 目录存在
					let result = FS.readdirSync(dirPath)
					console.warn(`查看${fileMonth}文件列表`, result)
					isOpenConsole ? console.table(result) : ""
					that.setData({
						monthFileList: result
					})
					resolve(result)
				},
				fail(err) {
					// 文件不存在或其他错误
					console.error("getMonthFileList-文件目录还不存在的呦", err)
					wx.showToast({
						title: "本月还没有开始记录呦",
						icon: "none"
					})
					that.setData({
						monthFileList: []
					})
					reject()
				}
			})
		})
	},

	// 统计分享本月账单
	shareMonthFile() {
		let that = this
		let dirData = this.getTodayFilePath()
		let downFileList = FS.readdirSync(dirData.dirName) // 本月文件目录下所有文件列表
		let nowMonthTotalDataFileName = dirData.dateMonth + "-合计" + FILETYPE // 月份合计

		// 无文件可提取
		if (downFileList.length <= 0) {
			return wx.showToast({
				title: "还没有开始记账哝，保持住好习惯",
				icon: "none",
				duration: 5000
			})
		}

		wx.showModal({
			title: "谨慎操作！",
			content: `请确认是否要对${dirData.dateMonth}月份的账单进行统计！`,
			success: function (res) {
				if (res.confirm) {
					// 统计本月所有数据并生成文件分享
					let nowMonthTotalData = []
					wx.showLoading({
						title: "正在统计...",
					})
					try {
						downFileList.forEach((fileName, fileIndex) => {
							console.log("正在读取文件...", fileName)
							// 剔除原合计文件
							if (fileName == nowMonthTotalDataFileName) {
								that.removeFile(dirData.dirName + "/" + nowMonthTotalDataFileName)
							}
							// 读取每日文件数据
							FS.readFile({
								filePath: dirData.dirName + "/" + fileName,
								encoding: 'utf8',
								position: 0,
								success(nowData) {
									let dayName = fileName.split(".")[0]
									nowData = nowData.data ? JSON.parse(nowData.data) : nowData.data
									console.log(nowData)
									nowMonthTotalData.push({
										[dayName]: nowData
									})
									console.log(`${dayName}文件数据提取完成`, fileIndex,
										downFileList.length - 1, nowMonthTotalData)
									// 数据提取完成
									if (fileIndex >= downFileList.length - 1) {
										FS.writeFile({
											filePath: dirData.dirName + "/" + nowMonthTotalDataFileName,
											data: JSON.stringify(nowMonthTotalData),
											encoding: 'utf8',
											success(writeRes) {
												console.log(nowMonthTotalDataFileName + "月份统计文件创建成功", writeRes)
												wx.hideLoading()
												that.getFileList()
												wx.showModal({
													title: "爱你呦！",
													content: "现在就要给他分享嘛",
													success(shareRes) {
														if (shareRes.confirm) {
															that.getFileList()
															wx.shareFileMessage({
																filePath: dirData.dirName + "/" + nowMonthTotalDataFileName,
																fileName: nowMonthTotalDataFileName,
																success: () => {
																	console.log('分享文件成功');
																	wx.showToast({
																		title: "已完成分享哝！快去跟他吐槽吧。",
																		icon: "none",
																		duration: 5000
																	})
																},
																fail: (shareErr) => {
																	console.log('分享文件失败', shareErr);
																	if (shareErr.errMsg && shareErr.errMsg.indexOf("fail canceled")) {
																		wx.showToast({
																			title: '咋还取消分享了呢',
																			icon: "none"
																		})
																	} else {
																		wx.showToast({
																			title: "CPU要着火啦，快联系小李同学灭火",
																			icon: "none",
																			duration: 5000
																		})
																	}
																}
															});
														} else if (shareRes.cancel) {
															console.log('用户点击取消');
														}
													}
												})
											},
											fail(writeErr) {
												console.error("本月数据统计失败", writeErr)
												wx.hideLoading()
												wx.showToast({
													title: "本月数据统计失败，快请小李同学！",
													icon: "none",
													duration: 5000
												})
											}
										})
									}
								},
								fail(nowErr) {
									console.error(`shareMonthFile-showModal-readFile==${fileName}`, nowErr)
									wx.hideLoading()
									wx.showToast({
										title: `${fileName}文件提取失败`,
										iicon: "none"
									})
								}
							})
						})
					} catch (tryCatchErr) {
						//TODO handle the exception
						console.error("查看捕获到的统计错误", tryCatchErr)
					}
				} else if (res.cancel) {
					console.log('用户点击取消');
				}
			}
		})
	},
	// 获取小程序本地用户文件的缓存大小
	getStorageSize: function () {
		if (this.data.isScanning) return

		this.setData({
			isScanning: true,
			files: [],
			scannedFolders: 0
		})

		this.scanDirectory(wx.env.USER_DATA_PATH, '')
	},

	scanDirectory: function (currentPath, relativePath) {
		const that = this
		const fs = wx.getFileSystemManager()

		try {
			const items = fs.readdirSync(currentPath)
			console.log("正在统计文件目录", items)
			items.forEach(itemName => {
				if (!that.data.isScanning) return

				const fullPath = `${currentPath}/${itemName}`
				const newRelativePath = relativePath ? `${relativePath}/${itemName}` : itemName

				try {
					const stats = fs.statSync(fullPath)
					if (stats.isDirectory()) {
						that.scanDirectory(fullPath, newRelativePath)
					} else {
						const size = stats.size
						const sizeDisplay = that.formatFileSize(size)
						console.warn(`${fullPath}文件大小b`, size, sizeDisplay)

						that.data.files.push({
							name: itemName,
							path: fullPath,
							size: sizeDisplay
						})
					}
				} catch (error) {
					console.warn('无法访问：', itemName)
				}
			})

			that.setData({
				scannedFolders: that.data.scannedFolders + 1
			})

		} catch (error) {
			console.error('读取目录失败：', currentPath)
		}

		if (currentPath === wx.env.USER_DATA_PATH) {
			that.setData({
				isScanning: false
			})
			that.updateSummary()
		}
	},

	formatFileSize: function (bytes) {
		if (bytes === 0) return '0 B'

		const k = 1024
		const sizes = ['B', 'KB', 'MB', 'GB']
		const i = Math.floor(Math.log(bytes) / Math.log(k))

		return parseFloat((bytes / Math.pow(k, i)).toFixed(2)) + ' ' + sizes[i]
	},

	updateSummary: function () {
		console.log("统计完成，计算文件占用大小", this.data.files)
		const totalBytes = this.data.files.reduce((sum, file) => {
			const sizeStr = file.size.split(' ')[0]
			const unit = file.size.split(' ')[1]
			let multiplier = 1

			switch (unit) {
				case 'KB':
					multiplier = 1024;
					break
				case 'MB':
					multiplier = 1024 * 1024;
					break
				case 'GB':
					multiplier = 1024 * 1024 * 1024;
					break
			}

			return sum + (parseFloat(sizeStr) * multiplier)
		}, 0)
		console.log("查看统计完成后，占用空间 byte", totalBytes)
		this.setData({
			totalSize: this.formatFileSize(totalBytes)
		})
	},
	// 将字节转换为更友好的单位
	toFileFormatSize(bytes) {
		if (bytes < 1024) return bytes + ' B';
		else if (bytes < 1048576) return (bytes / 1024).toFixed(2) + ' KB';
		else return (bytes / 1048576).toFixed(2) + ' MB';
	},
})